﻿package com.htmlparser;

import java.io.ByteArrayOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.UnsupportedEncodingException;

import org.htmlparser.Node;
import org.htmlparser.NodeFilter;
import org.htmlparser.Parser;
import org.htmlparser.filters.NodeClassFilter;
import org.htmlparser.filters.TagNameFilter;
import org.htmlparser.nodes.TextNode;
import org.htmlparser.tags.BodyTag;
import org.htmlparser.tags.Div;
import org.htmlparser.tags.FormTag;
import org.htmlparser.tags.ImageTag;
import org.htmlparser.tags.InputTag;
import org.htmlparser.tags.LinkTag;
import org.htmlparser.tags.OptionTag;
import org.htmlparser.tags.ScriptTag;
import org.htmlparser.tags.SelectTag;
import org.htmlparser.tags.TableColumn;
import org.htmlparser.tags.TableRow;
import org.htmlparser.tags.TableTag;
import org.htmlparser.tags.TextareaTag;
import org.htmlparser.util.NodeList;
import org.jdom.Document;
import org.jdom.Element;
import org.jdom.output.Format;
import org.jdom.output.XMLOutputter;

public class Parse {
	
	
	static String htmltext = "";
//	public static void main(String[] args) {
//		String srcUrl = "E:\\USERS\\java\\aa.htm";
//		String destUrl = "E:\\USERS\\java\\aaTest.xml";
////		String srcUrl = "E:\\USERS\\java\\testOA.html";
////		String destUrl = "E:\\USERS\\java\\tableTestOA.xml";
//		try {
//			getContent(srcUrl, destUrl);
//		} catch (Exception e) {
//			e.printStackTrace();
//		}
//	}
//	
	//提取网页中的表格table
	public static String getContent(String srcUrl) throws Exception {
		int id = 0;//table的序号
		//srcUrl =  srcUrl.replaceAll("/", "\\\\");
		//String path = System.getProperty("user.dir").replaceAll("\\bin", "") + srcUrl;
		//System.out.println("path=====" + path);
		Parser parser = new Parser(srcUrl);
		System.out.println("Encodeing  parser  =====" + parser.getEncoding());        /////////////
		parser.setEncoding("gb2312");           /////////////
System.out.println("Encodeing=====" + parser.getEncoding());
		TagNameFilter tableFilter = new TagNameFilter("table");
		NodeList nodelist = parser.extractAllNodesThatMatch(tableFilter);

		// 用parser取不到divList，必须另建一个Parser
		Parser parser2 = new Parser(srcUrl);
		parser2.setEncoding("gb2312"); ////////////
		NodeFilter divFilter = new NodeClassFilter(Div.class);
		// TagNameFilter divFilter = new TagNameFilter("div");
		NodeList divList = parser2.extractAllNodesThatMatch(divFilter);
		//System.out.println("divList : " + divList);

		Element data = new Element("data");
		Document document = new Document(data);

		if (nodelist != null) {
			for (int i = 0; i <= nodelist.size(); i++) {
				if (nodelist.elementAt(i) instanceof TableTag) {
					
					//过滤嵌套在div或者table里的table，以免解析出重复的talbe
					if (!(nodelist.elementAt(i).getParent() instanceof Div)
							&& !(nodelist.elementAt(i).getParent() instanceof TableColumn)) {
						id++;
						Element table = getTable((TableTag)(nodelist.elementAt(i)));
						data.addContent(table);
					}
				}
			}
		}
		
		// 提取没有嵌套在table里的Div
		if (divList != null) {
			int index = 0;
			for (int i = 0; i < divList.size(); i++) {
				// divNode: 某个没有嵌套在table里的div
				Node divNode = divList.elementAt(i);

				if (divNode instanceof Div
						&& (divNode.getParent() instanceof BodyTag)) {
					index++;
					Element div = getDiv((Div)divNode);
					data.addContent(div);
				}
			}
		}
		System.out.println("document:"+document.getBaseURI());
		//XMLOutputter outp = new XMLOutputter(Format.getPrettyFormat());
		        //outp.output(document, System.out); //  输出XML文档
		//outp.output(document, new FileOutputStream(destUrl)); //  输出XML文档。
		       //new FileOutputStream("e:\\table2.xml")
		System.out.println("XML 文档生成完毕！");
		
		//测试输出的字符串
//		System.out.println("++++++++++++++++++++++++++++++++++");
//		System.out.println(doc2String(data));
//		System.out.println("++++++++++++++++++++++++++++++++++");
		
		htmltext =doc2String(data);
		return htmltext;
	}


	// td或Div里的嵌套表格table
	public static Element getTable(TableTag table){
		TableTag innerTable = table;
		TableRow[] rows = innerTable.getRows();
		Element Inner_table = new Element("T");

		//遍历所有行
		for (int j = 0; j < rows.length; j++) {// tr
			TableRow row = (TableRow) rows[j];
			
			//取得当前行的所有列
			TableColumn[] columns = row.getColumns();
			
			//遍历当前列的所有子节点
			for (int k = 0; k < columns.length; k++) {// td
				Element d = new Element("d");
				d.setAttribute("r", String.valueOf(j));
				d.setAttribute("c", String.valueOf(k));
				
				//nodeList2:当前列的所有子节点的集合�
				NodeList nodeList2 = columns[k].getChildren();
				if (nodeList2 != null) {	
					d = MyGet(nodeList2, d);
				}// td
				Inner_table.setAttribute("r",String.valueOf(rows.length));
				Inner_table.setAttribute("c",String.valueOf(columns.length));
				Inner_table.addContent(d);
			}
		}// tr
		return Inner_table;
	}
	
	//提取超链接�
	public static Element getLink(LinkTag linkTag){
		LinkTag link = linkTag;
		Element a = new Element("a");
		Element link2 = new Element("link");
		Element link_text = new Element("tx");

		// 判断是否用图片作为超链接
		if (link.getFirstChild() instanceof ImageTag) {
			Element a_img = new Element("img");
			a_img.setText(((ImageTag) link.getFirstChild()).extractImageLocn());
			link_text.addContent(a_img);
		} else {
			link_text.setText(((LinkTag) link).getLinkText());
		}
		link2.setText( link.extractLink());
		a.addContent(link2);
		//a.addContent(link_text);
		return a;
	}
	
	//提取图片
//	public static Element getImage(ImageTag imageTag){
//		ImageTag image = imageTag;
//		Element img = new Element("img");
//		img.setText(image.extractImageLocn());
//		return img;
//	}
	
	//提取表单
	public static Element getInput(InputTag inputTag){
		InputTag input2 = inputTag;
		Element input = null;
		String input_type = (input2.getAttribute("type"));
		String input_value = (input2.getAttribute("value"));
		String input_name = (input2.getAttribute("name"));
		
		if (input_type.equals("text")) {
			input = new Element("in");
		} else if (input_type.equals("radio")) {
			input = new Element("rd");
			if (input2.getAttribute("checked") != null) {
				String checked = input2.getAttribute("checked").toString();
				input.setAttribute("checked",checked);
			}
			if (input2.getAttribute("value") != null) {
				String value = input2.getAttribute("value").toString();
				//input.setAttribute("v",checked);
				input.setText(value);
			}
			//input.setText(input2.toPlainTextString());
		} else if (input_type.equals("checkbox")) {
			input = new Element("cb");
		} else if (input_type.equals("submit")) {
			input = new Element("smt");
		} else if (input_type.equals("reset")) {
			input = new Element("rst");
		} else if (input_type.equals("button")) {
			input = new Element("bt");
			
			String temp_button_href = input2.getAttribute("onclick");
;
			//取input button中的链接地址
			int ii = temp_button_href.indexOf("(");
			int jj = temp_button_href.indexOf(")");
			String button_href = temp_button_href.substring(ii + 1, jj).replaceAll("'", "");
			
			if (temp_button_href != null) {
				input.setAttribute("location.href", button_href);
			}
		}

		if (input != null ) {
			if (input_value != null&& !input_value.equals("")) {
				input.setText(input_value);
			} else if (input_name != null && !input_name.equals("")) {
				input.setText(input_name);
			}
		}	
		return input;
	}
	
	//提取多行文本域�
	public static Element getTextarea(TextareaTag textareaTag){
		TextareaTag textarea2 = textareaTag;
		Element textarea = new Element("ta");
		textarea.setText(textarea2.getValue());

		return textarea;
	}
	
	//提取嵌套Div
	public static Element getDiv(Div divTag) throws Exception {
		Div div2 = divTag;
		Element div = new Element("div");
		NodeList nodeList = div2.getChildren();
		if(nodeList!=null){
			div	= MyGet(nodeList, div);
		}	
		return div;
	}
	
	//提取纯文本�
	public static Element getText2(TextNode textNode){
		TextNode text2 = textNode;
		String temp = text2.getText().trim();
		//String result = temp.replaceAll("&#xD;", "");
		String result = temp.replaceAll("&nbsp;", "");
		Element text = new Element("tx");
		text.setText(result);

		return text;
	}
	
	//提取下拉列表
	public static Element getSelect(SelectTag selectTag){
		SelectTag select2= selectTag;
		Element select = new Element("s");
		NodeList selectList = select2.getChildren();
		
		for (int i = 0; i < selectList.size(); i++) {
			if (selectList.elementAt(i) instanceof OptionTag) {
				Element option = new Element("o");
				OptionTag optionTag = (OptionTag) selectList.elementAt(i);
				option.setAttribute("v",optionTag.getAttribute("value"));
		
				if (optionTag.getAttribute("selected") != null) {
					String selected = optionTag.getAttribute("selected").toString();
					option.setAttribute("selected",selected);
				}
				option.setText(optionTag.getOptionText());
				select.addContent(option);
			}
		}
		return select;
	}
	
	//提取form表单
	public static Element getForm(FormTag formTag){
		FormTag form2 = formTag;
		Element form = new Element("form");
		NodeList nodeList = form2.getChildren();
		
		if (nodeList != null) {
			form = MyGet(nodeList, form);
		}
		return form;
	}
	
	//综合标签判断
	public static Element MyGet(NodeList nl, Element e){
		NodeList nodeList = nl;
		Element element = e;
		if (nodeList != null) {
			for (int i = 0; i < nodeList.size(); i++) {
				Node node = nodeList.elementAt(i);
		
				// 处理图片
//				if (node instanceof ImageTag) {
//					Element img = getImage((ImageTag)node);
//					element.addContent(img);
//				}
		
				// 处理超链接�
				if (node instanceof LinkTag) {
					Element link = getLink((LinkTag)node);
					element.addContent(link);
				}
				
				// 处理输入表单input
				else if (node instanceof InputTag) {
					Element input = getInput((InputTag)node);
					if(input != null){
						element.addContent(input);
					}																		
				}

				// 处理多行文本域textarea
				else if (node instanceof TextareaTag) {
					Element textarea = getTextarea((TextareaTag)node);
					element.addContent(textarea);
				}
				
				// 处理下拉列表
				else if (node instanceof SelectTag) {
					Element select = getSelect((SelectTag)node);
					element.addContent(select);
				}
				
				// 处理表格table
				else if (node instanceof TableTag) {
					if (getTable((TableTag)node) != null) {
						Element table = getTable((TableTag)node);
						element.addContent(table);
					}
				}
				
				//处理div
				else if (node instanceof Div) {
					try {
						Element div3 = getDiv((Div)node);
						element.addContent(div3);
					} catch (Exception ex) {
						ex.printStackTrace();
					}
				}
				
				//纯文本�
				else if ((node instanceof TextNode) && (!node.getText().trim().equals(""))) {
					Element text = getText2((TextNode)node);
					element.addContent(text);
				}
				
				// 处理form
				else if (node instanceof FormTag) {
					Element form = getForm((FormTag)node);
					element.addContent(form);
				}
				
				//有标签的文本
				else if((node.getFirstChild()!= null)&&(!node.getText().trim().equals(""))&&(!(node instanceof ScriptTag))){
					String result = node.toPlainTextString();
					if (!result.equals("")) {
						Element text = new Element("tx");
						text.setText(result);
						element.addContent(text);
					}
				}
			}
		}
		return element;
	}
	
	/**
	 *   把xml Document对象转换成字符串
	 *   
	 * @param doc 需要转换的Document
	 * @return    返回xml Document对象转换成的String
	 */
	public static String doc2String(Element data) {

	    Format format = Format.getCompactFormat();
	    format.setEncoding("GBK");//设置xml文件的字符为gb2312，解决中文问题
	    XMLOutputter xmlout = new XMLOutputter(format);
	    ByteArrayOutputStream bo = new ByteArrayOutputStream();
	    try {
			xmlout.output(data,bo);
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		  String xmlStr = bo.toString(); 
		    
		  return xmlStr;     
	}
	
	
}
